
<template>
  <el-form :rules="rules" :model='item' ref='structForm' class="position-2d">
    <el-popover popper-class='map-popper' placement="bottom" width="262" trigger="click" @show="openPopover">
      <div class="map" @click="choosePoint" :style="{'background-image': `url(${prop.backgroundImage})`}" ref="map">
        <div class="confirm point" :style="{'top': confirmPoint.y - 8 + 'px', 'left': confirmPoint.x - 8 + 'px', 'background-image': `url(${prop.crossPointImage})`}"></div>
      </div>
      <div class="ymax">{{ prop.yAxisMax }}</div>
      <div class="xmax">{{ prop.xAxisMax }}</div>
      <el-form-item slot="reference" prop="value" :label="prop.paramName">
        <el-input value="" ref="mapInput"></el-input>
      </el-form-item>
    </el-popover>
    <div class="tool-bar">
      <svg-icon :icon-class="`参数${item.openParam.isOpen ? '已' : '未'}开放`" :className="`${item.openParam.isOpen} signal-open`" @click="paramOpen(item)"/>
    </div>
  </el-form>
</template>

<script>
import Platform from '@/utils/platform'

export default {
  name: 'position2D',
  props: {
    item: {
      required: true,
      type: Object,
      default: () => {}
    },
    prop: {
      required: true,
      type: Object,
      default: () => {
        return {
          yAxisMax: 0
        }
      }
    }
  },
  data() {
    return {
      xHeight: 0, // 节点间距
      yHeight: 0,
      pointList: [],
      confirmPoint: {}, // 点击节点位置
      rules: {
        value: [{ required: true, message: ' ', trigger: 'blur' }]
      }
    }
  },
  mounted() {
    this.initPointList()

    this.mapInputDOM = this.$refs.mapInput.$el.getElementsByTagName('input')[0]
    if ((!Platform.IS_FIREFOX) && (!Platform.IS_SAFARI)) {
      // 输入框手动禁用（为了保留element表单校验提示红框）
      // this.mapInputDOM.setAttribute('disabled', true)
    }

    if (this.item.value !== null) {
      this.initPointItem()
    }
  },
  methods: {
    // 初始化可选节点列表
    initPointList() {
      const xPoint = (this.prop.xAxisMax - this.prop.xAxisMin) / this.prop.xAxisStep
      this.xHeight = 200 / xPoint
      const yPoint = (this.prop.yAxisMax - this.prop.yAxisMin) / this.prop.yAxisStep
      this.yHeight = 200 / yPoint
      for (let x = 0; x <= xPoint; x++) {
        for (let y = 0; y <= yPoint; y++) {
          this.pointList.push({ x: x * this.xHeight, y: y * this.yHeight })
        }
      }
    },
    // 初始化已选节点
    initPointItem() {
      const xref = this.$parent.$parent.$refs.structItem.find(item => item.item.paramKey === this.prop.x)
      const yref = this.$parent.$parent.$refs.structItem.find(item => item.item.paramKey === this.prop.y)
      this.confirmPoint = {
        x: (xref.item.value - this.prop.xAxisMin) / this.prop.xAxisStep * this.xHeight,
        y: (this.prop.yAxisMax - yref.item.value) / this.prop.yAxisStep * this.yHeight
      }
      setTimeout(() => {
        this.mapInputDOM.value = `{ x: ${xref.item.value}, y: ${yref.item.value} }`
      }, 0)
    },
    openPopover() {
    },
    choosePoint(e) {
      const point = this.pointList.find(item => {
        return item.x - this.xHeight / 2 <= e.clientX - this.$refs.map.getBoundingClientRect().x &&
        e.clientX - this.$refs.map.getBoundingClientRect().x <= item.x + this.xHeight / 2 &&
        item.y - this.yHeight / 2 <= e.clientY - this.$refs.map.getBoundingClientRect().y &&
        e.clientY - this.$refs.map.getBoundingClientRect().y <= item.y + this.yHeight / 2
      })
      if (point) { this.confirmPoint = point }
      const value = {
        x: this.confirmPoint.x / this.xHeight * this.prop.xAxisStep + this.prop.xAxisMin,
        y: this.prop.yAxisMax - this.confirmPoint.y / this.yHeight * this.prop.yAxisStep
      }
      const newItem = this.item
      if (this.prop.x === newItem.paramKey) {
        newItem.value = value.x
      } else {
        newItem.value = value.y
      }
      setTimeout(() => {
        this.mapInputDOM.value = `{ x: ${value.x}, y: ${value.y} }`
      }, 0)
      this.$emit('update:item', newItem)
      const xref = this.$parent.$parent.$refs.structItem.find(item => item.item.paramKey === this.prop.x)
      const yref = this.$parent.$parent.$refs.structItem.find(item => item.item.paramKey === this.prop.y)
      xref.item.value = value.x
      yref.item.value = value.y
    },
    paramOpen(item) {
      const newItem = item
      newItem.showParamOpen = !item.showParamOpen
      this.$emit('update:item', newItem)
    }
  }
}
</script>

<style lang="scss">
.el-form-item.is-error .position-2d .el-input.is-disabled .el-input__inner{
  border-color: #E15863;
}
.el-drawer .el-form--label-top .position-2d .el-form-item{
  margin-bottom: 8px;
}
.position-2d {
  display: flex;
  span{
    flex: 1 0 auto;
  }
  .el-input.is-disabled{
    .el-input__inner{
      background-color: #fff;
      color: #1f1f1f;
      cursor: pointer;
    }
  }
  .tool-bar{
    margin-top: 36px;
    .signal-open{
      width: 16px;
      height: 32px;
      cursor: pointer;
      margin-left: 24px;
      margin-right: 2px;
      &.true{
        width: 18px;
        margin-right: 0;
      }
    }
  }
}
.map-popper{
  padding: 30px;
  .map{
    height: 200px;
    background-size: 100% 100%;
    background-repeat: no-repeat;
    position: relative;
    .point{
      position: absolute;
      width: 16px;
      height: 16px;
      background-size: 0 0;
      &.confirm{
        background-size: 100% 100%;
        background-color: #49c469;
        // box-shadow: 0 0 12px 2px rgba($color: #1c552b, $alpha: 0.5);
      }
    }
  }
  .ymax{
    position: absolute;
    top: 22px;
    left: -2px;
    width: 34px;
    text-align: center;
  }
  .xmax{
    position: absolute;
    bottom: 10px;
    right: 10px;
    width: 40px;
    text-align: center;
  }
}
</style>
